package cn.c4ad.voa;

import java.io.File;

import android.app.ActionBar;
import android.app.Activity;
import android.app.DownloadManager;
import android.app.LoaderManager.LoaderCallbacks;
import android.content.ContentResolver;
import android.content.ContentUris;
import android.content.ContentValues;
import android.content.CursorLoader;
import android.content.Loader;
import android.database.ContentObserver;
import android.database.Cursor;
import android.media.MediaPlayer;
import android.media.MediaPlayer.OnCompletionListener;
import android.media.MediaPlayer.OnPreparedListener;
import android.media.MediaPlayer.OnTimedTextListener;
import android.media.TimedText;
import android.net.Uri;
import android.os.AsyncTask;
import android.os.Bundle;
import android.os.Handler;
import android.text.TextUtils;
import android.view.ActionMode;
import android.view.ActionMode.Callback;
import android.view.Menu;
import android.view.MenuItem;
import android.view.View;
import android.widget.TextView;
import android.widget.Toast;

public class ArticalActivity extends Activity {
	public static final String EXTRA_URI = "uri";
	public static final String EXTRA_ID = "id";

	private ContentResolver mContentResolver;

	private TextView mRightButton;
	private TextView mArticalContent;
	private LoadArticalTask mLoadArticalTask;

	private MediaPlayer mMediaPlayer;

	private Uri mArticalUri;
	private Cursor mArticalCursor;

	private Loader<Cursor> mLoader;

	private ContentObserver mContentObserver;

	private boolean mLoadFinished = false;

	private Model.ArticalTypeParameter mParameter;

	@Override
	protected void onCreate(Bundle savedInstanceState) {
		super.onCreate(savedInstanceState);

		setContentView(R.layout.artical_activity);

		VoaContentProvider.checkDictionaryDatabase(ArticalActivity.this);

		ActionBar actionBar = getActionBar();
		actionBar.setDisplayOptions(ActionBar.DISPLAY_SHOW_CUSTOM);
		actionBar.setCustomView(R.layout.main_activity_action_bar);

		View actionBarView = actionBar.getCustomView();
		TextView title = (TextView) actionBarView.findViewById(R.id.title);
		title.setText(R.string.artical);

		mRightButton = (TextView) actionBarView.findViewById(R.id.rightButton);
		mRightButton.setVisibility(View.GONE);

		mArticalContent = (TextView) findViewById(R.id.content);
		mArticalContent
				.setCustomSelectionActionModeCallback(mSelectionCallback);

		TextView leftButton = (TextView) actionBarView
				.findViewById(R.id.leftButton);
		leftButton.setVisibility(View.VISIBLE);
		leftButton.setText(R.string.back);
		leftButton.setOnClickListener(new View.OnClickListener() {
			@Override
			public void onClick(View view) {
				finish();
			}
		});

		long id = getIntent().getLongExtra(EXTRA_ID, -1);
		if (id >= 0) {
			mArticalUri = ContentUris.withAppendedId(
					VoaContentProvider.ARTICAL_CONTENT_URI, id);

			mLoader = getLoaderManager().initLoader(0, null,
					new LoaderCallbacks<Cursor>() {
						@Override
						public Loader<Cursor> onCreateLoader(int id,
								Bundle bundle) {
							return new CursorLoader(ArticalActivity.this,
									mArticalUri, null, null, null, null);
						}

						@Override
						public void onLoadFinished(Loader<Cursor> loader,
								Cursor cursor) {
							if (mArticalCursor != null) {
								mArticalCursor.close();
								mArticalCursor = null;
							}

							if (cursor != null && cursor.moveToFirst()) {
								mArticalCursor = cursor;
								int downloadState = mArticalCursor.getInt(mArticalCursor
										.getColumnIndex(VoaContentProvider.DOWNLOAD_STATE));
								int type = mArticalCursor.getInt(mArticalCursor
										.getColumnIndex(VoaContentProvider.TYPE));
								mParameter = Model
										.getArticalTypeParameter(type);

								if (!mLoadFinished
										&& mArticalCursor != null
										&& downloadState == VoaContentProvider.DOWNLOAD_STATE_NULL
										&& mLoadArticalTask == null) {
									mLoadArticalTask = new LoadArticalTask();
									mLoadArticalTask.execute(0);
								}
							}

							mLoadFinished = true;
							refreshUi();
						}

						@Override
						public void onLoaderReset(Loader<Cursor> loader) {
						}
					});

			mContentObserver = new ContentObserver(new Handler()) {
				@Override
				public void onChange(boolean selfChange) {
					super.onChange(selfChange);
					mLoader.forceLoad();
				}
			};
			mContentResolver = getContentResolver();
			mContentResolver.registerContentObserver(
					VoaContentProvider.ARTICAL_CONTENT_URI, true,
					mContentObserver);
		}
	}

	@Override
	protected void onResume() {
		super.onResume();
	}

	@Override
	protected void onPause() {
		super.onPause();
	}

	@Override
	protected void onDestroy() {
		if (mMediaPlayer != null) {
			mMediaPlayer.pause();
			mMediaPlayer.release();
			mMediaPlayer = null;
		}

		if (mContentResolver != null) {
			mContentResolver.unregisterContentObserver(mContentObserver);
		}

		if (mArticalCursor != null) {
			mArticalCursor.close();
			mArticalCursor = null;
		}

		super.onDestroy();
	}

	private void refreshUi() {
		if (mParameter != null) {
			ActionBar actionBar = getActionBar();
			View actionBarView = actionBar.getCustomView();
			TextView title = (TextView) actionBarView.findViewById(R.id.title);
			title.setText(mParameter.fragmentTitleResId);
		}

		TextView headView = (TextView) findViewById(R.id.head);
		TextView contentView = (TextView) findViewById(R.id.content);
		TextView hintView = (TextView) findViewById(R.id.hint);
		View scroll = findViewById(R.id.scrollView);

		if (mArticalCursor != null && mArticalCursor.moveToFirst()) {
			int downloadState = mArticalCursor.getInt(mArticalCursor
					.getColumnIndex(VoaContentProvider.DOWNLOAD_STATE));
			if (downloadState == VoaContentProvider.DOWNLOAD_STATE_NULL) {
				if (mLoadArticalTask == null) {
					mRightButton.setVisibility(View.VISIBLE);
					mRightButton.setText(R.string.download);
					mRightButton.setOnClickListener(new View.OnClickListener() {
						@Override
						public void onClick(View arg0) {
							if (mLoadArticalTask == null && mArticalUri != null) {
								mLoadArticalTask = new LoadArticalTask();
								mLoadArticalTask.execute(0);
								refreshUi();
							}
						}
					});
					hintView.setVisibility(View.VISIBLE);
					hintView.setText(R.string.hint_download_artical);
					scroll.setVisibility(View.GONE);
				} else {
					mRightButton.setVisibility(View.VISIBLE);
					mRightButton.setText(R.string.downloading);
					mRightButton.setOnClickListener(null);
					hintView.setVisibility(View.VISIBLE);
					hintView.setText(R.string.downloading_net);
					scroll.setVisibility(View.GONE);
				}
			} else if (downloadState == VoaContentProvider.DOWNLOAD_STATE_COMPLETED_TEXT) {
				mRightButton.setVisibility(View.VISIBLE);
				mRightButton.setText(R.string.download_mp3);
				mRightButton.setOnClickListener(new View.OnClickListener() {
					@Override
					public void onClick(View arg0) {
						long downloadId = startDownloadMp3();
						if (downloadId > 0) {
							ContentValues values = new ContentValues();
							values.put(VoaContentProvider.DOWNLOAD_ID,
									downloadId);
							values.put(
									VoaContentProvider.DOWNLOAD_STATE,
									VoaContentProvider.DOWNLOAD_STATE_LOADING_MP3);
							mContentResolver.update(mArticalUri, values, null,
									null);

							// refreshUi();
						}
					}
				});

				hintView.setVisibility(View.GONE);
				scroll.setVisibility(View.VISIBLE);

				headView.setText(mArticalCursor.getString(mArticalCursor
						.getColumnIndex(VoaContentProvider.HEAD)));
				contentView.setText(mArticalCursor.getString(mArticalCursor
						.getColumnIndex(VoaContentProvider.CONTENT)));
			} else if (downloadState == VoaContentProvider.DOWNLOAD_STATE_LOADING_MP3) {
				mRightButton.setVisibility(View.VISIBLE);
				mRightButton.setText(R.string.download_cancel);
				mRightButton.setOnClickListener(new View.OnClickListener() {
					@Override
					public void onClick(View view) {
						long downloadId = mArticalCursor.getLong(mArticalCursor
								.getColumnIndex(VoaContentProvider.DOWNLOAD_ID));
						if (downloadId > 0) {
							DownloadManager downloadManager = (DownloadManager) getSystemService(DOWNLOAD_SERVICE);
							downloadManager.remove(downloadId);

							ContentValues values = new ContentValues();
							values.put(VoaContentProvider.DOWNLOAD_ID, 0);
							values.put(
									VoaContentProvider.DOWNLOAD_STATE,
									VoaContentProvider.DOWNLOAD_STATE_COMPLETED_TEXT);
							mContentResolver.update(mArticalUri, values, null,
									null);

							// refreshUi();
						}
					}
				});

				hintView.setVisibility(View.GONE);
				scroll.setVisibility(View.VISIBLE);

				headView.setText(mArticalCursor.getString(mArticalCursor
						.getColumnIndex(VoaContentProvider.HEAD)));
				contentView.setText(mArticalCursor.getString(mArticalCursor
						.getColumnIndex(VoaContentProvider.CONTENT)));
			} else if (downloadState == VoaContentProvider.DOWNLOAD_STATE_COMPLETED_ALL) {
				if (mMediaPlayer != null) {
					mRightButton.setVisibility(View.VISIBLE);
					mRightButton.setText(R.string.stop_mp3);
					mRightButton.setOnClickListener(new View.OnClickListener() {
						@Override
						public void onClick(View view) {
							if (mMediaPlayer != null) {
								mMediaPlayer.pause();
								mMediaPlayer.release();
								mMediaPlayer = null;
								refreshUi();
							}
						}
					});
				} else {
					mRightButton.setVisibility(View.VISIBLE);
					mRightButton.setText(R.string.play_mp3);
					mRightButton.setOnClickListener(new View.OnClickListener() {
						@Override
						public void onClick(View view) {
							if (mMediaPlayer == null) {
								mMediaPlayer = startMediaPlayer();
								refreshUi();
							}
						}
					});
				}

				hintView.setVisibility(View.GONE);
				scroll.setVisibility(View.VISIBLE);

				headView.setText(mArticalCursor.getString(mArticalCursor
						.getColumnIndex(VoaContentProvider.HEAD)));
				contentView.setText(mArticalCursor.getString(mArticalCursor
						.getColumnIndex(VoaContentProvider.CONTENT)));
			} else {
				mRightButton.setVisibility(View.GONE);
				hintView.setVisibility(View.VISIBLE);
				hintView.setText(R.string.error);
				scroll.setVisibility(View.GONE);
			}
		} else {
			mRightButton.setVisibility(View.GONE);
			hintView.setVisibility(View.VISIBLE);
			if (mLoadFinished) {
				hintView.setText(R.string.error);
			} else {
				hintView.setText(R.string.downloading);
			}
			scroll.setVisibility(View.GONE);
		}
	}

	private class LoadArticalTask extends AsyncTask<Integer, Integer, Integer> {
		String url;
		Uri uri;

		@Override
		protected void onPreExecute() {
			super.onPreExecute();
			url = mArticalCursor.getString(mArticalCursor
					.getColumnIndex(VoaContentProvider.URL));
			uri = mArticalUri;
		}

		@Override
		protected Integer doInBackground(Integer... arg0) {
			String[] artical = Model.getArticalContent(url,
					mParameter.articalUrlHead, mParameter.headRegex,
					mParameter.mp3urlRegex, mParameter.contentStart,
					mParameter.contentEnd);
			String head = artical[0];
			String mp3url = artical[1];
			String content = artical[2];
			if (!TextUtils.isEmpty(mp3url)) {
				int downloadState = VoaContentProvider.DOWNLOAD_STATE_COMPLETED_TEXT;
				ContentValues values = new ContentValues();
				values.put(VoaContentProvider.HEAD, head);
				values.put(VoaContentProvider.CONTENT, content);
				values.put(VoaContentProvider.MP3URL, mp3url);
				values.put(VoaContentProvider.DOWNLOAD_STATE, downloadState);
				mContentResolver.update(uri, values, null, null);
				return 0;
			}
			return 1;
		}

		@Override
		protected void onPostExecute(Integer result) {
			super.onPostExecute(result);
			mLoadArticalTask = null;
			if (result > 0) {
				refreshUi();
			}
		}
	}

	private long startDownloadMp3() {
		String url = null;
		if (mArticalCursor != null && mArticalCursor.moveToFirst()) {
			url = mArticalCursor.getString(mArticalCursor
					.getColumnIndex(VoaContentProvider.MP3URL));
		}

		if (TextUtils.isEmpty(url)) {
			return -1;
		}

		int nameStart = url.lastIndexOf("/");
		if (nameStart < 0) {
			return -1;
		}

		if (!url.endsWith(".mp3")) {
			return -1;
		}

		String name = Model.generateFileNameByUrl(url) + ".mp3";
		String path = "file://" + getExternalFilesDir(null).getPath()
				+ File.separator + name;
		Uri pathUri = Uri.parse(path);

		File file = new File(getExternalFilesDir(null), name);
		if (file.exists()) {
			file.delete();
		}

		DownloadManager downloadManager = (DownloadManager) getSystemService(DOWNLOAD_SERVICE);
		DownloadManager.Request request = new DownloadManager.Request(
				Uri.parse(url));
		request.setDestinationUri(pathUri);
		request.setNotificationVisibility(DownloadManager.Request.VISIBILITY_VISIBLE);
		return downloadManager.enqueue(request);
	}

	private MediaPlayer startMediaPlayer() {
		MediaPlayer mediaPlayer = null;
		try {
			String url = null;
			if (mArticalCursor != null && mArticalCursor.moveToFirst()) {
				url = mArticalCursor.getString(mArticalCursor
						.getColumnIndex(VoaContentProvider.MP3URL));
			}

			String name = Model.generateFileNameByUrl(url) + ".mp3";
			File file = new File(getExternalFilesDir(null), name);
			Uri fileUri = Uri.fromFile(file);
			mediaPlayer = new MediaPlayer();
			mediaPlayer.setOnPreparedListener(new OnPreparedListener() {
				@Override
				public void onPrepared(MediaPlayer m) {
					m.start();
				}
			});
			mediaPlayer.setOnCompletionListener(new OnCompletionListener() {
				@Override
				public void onCompletion(MediaPlayer mediaPlayer) {
					if (mArticalCursor != null && mArticalCursor.moveToFirst()) {
						long articalId = mArticalCursor.getLong(mArticalCursor
								.getColumnIndex(VoaContentProvider.ID));
						long time = System.currentTimeMillis();
						ContentValues values = new ContentValues();
						values.put(VoaContentProvider.ARTICAL_ID, articalId);
						values.put(VoaContentProvider.PLAY_TIME, time);
						mContentResolver.insert(
								VoaContentProvider.PLAY_CONTENT_URI, values);
					}
				}
			});
			mediaPlayer.setDataSource(ArticalActivity.this, fileUri);
			mediaPlayer.setLooping(true);
			mediaPlayer.prepare();
		} catch (Exception e) {
			if (mediaPlayer != null) {
				mediaPlayer.pause();
				mediaPlayer.release();
				mediaPlayer = null;
			}
		}

		return mediaPlayer;
	}

	private Callback mSelectionCallback = new Callback() {
		@Override
		public boolean onCreateActionMode(ActionMode actionMode, Menu menu) {
			menu.add(0, R.id.action_translate, 0, R.string.translate)
					.setIcon(R.drawable.action_translate)
					.setShowAsAction(
							MenuItem.SHOW_AS_ACTION_ALWAYS
									| MenuItem.SHOW_AS_ACTION_WITH_TEXT);
			return true;
		}

		@Override
		public boolean onPrepareActionMode(ActionMode actionMode, Menu menu) {
			return true;
		}

		@Override
		public boolean onActionItemClicked(ActionMode actionMode, MenuItem item) {
			if (item.getItemId() == R.id.action_translate) {
				int start = mArticalContent.getSelectionStart();
				int end = mArticalContent.getSelectionEnd();
				String word = mArticalContent.getText().subSequence(start, end)
						.toString();
				String meaning = VoaContentProvider.checkDictionary(
						ArticalActivity.this, word);
				if (!TextUtils.isEmpty(meaning)) {
					Toast.makeText(ArticalActivity.this, meaning,
							Toast.LENGTH_LONG).show();
				} else {
					Toast.makeText(ArticalActivity.this,
							R.string.translate_fail, Toast.LENGTH_SHORT).show();
				}
			}
			return true;
		}

		@Override
		public void onDestroyActionMode(ActionMode actionMode) {

		}
	};
}
